// -----------------------------
// Author: 		Dhaenens Gert	
// Creation: 	1/5/2015 10:53:28 PM				
// -----------------------------

#include "SoundSampler.h"

#include "SoundPlugin.h"
#include "SoundFilter.h"
#include "SoundPass.h"

SoundSampler::SoundSampler(UInt32 sampleRate)
	: m_SampleRate(sampleRate)
	, m_lpPlugin(nullptr)
{
}

SoundSampler::~SoundSampler()
{
	for (SoundFilter* lpFilter : m_Filters)
		delete lpFilter;
	for (SoundPass* lpPass : m_Passes)
		delete lpPass;

	delete m_lpPlugin;
}

SoundSample SoundSampler::Generate(Float frequency, Float amplitude, UInt8 harmonics, Float duration) const
{
	// Loop over the Filters & Reset them if they're not Global
	for (SoundFilter* lpFilter : m_Filters)
	{
		if (!lpFilter->IsGlobal)
			lpFilter->Reset();
	}

	// Create the Sample
	SoundSample sample = {};
	sample.Channels = 2;
	sample.SampleRate = m_SampleRate;
	sample.Count = (UInt32)(duration * sample.SampleRate * sample.Channels);
	sample.Samples = new Float[sample.Count];

	// Fill in the Samples
	for (UInt32 i = 0; i < sample.Count / sample.Channels; ++i)
	{
		Float t = (Float)i / sample.SampleRate;
		Float s = m_lpPlugin->Sample(frequency, amplitude, harmonics, t);

		Float leftChannel = s;
		Float rightChannel = s;

		for (SoundFilter* lpFilter : m_Filters)
			lpFilter->Apply(leftChannel, rightChannel, t, &leftChannel, &rightChannel);

		sample.Samples[i * 2 + 0] = leftChannel;
		sample.Samples[i * 2 + 1] = rightChannel;
	}

	// Apply the Passes
	for (SoundPass* lpPass : m_Passes)
		sample = lpPass->Apply(sample);

	return sample;
}
void SoundSampler::ResetFilters()
{
	for (SoundFilter* lpFilter : m_Filters)
		lpFilter->Reset();
}

void SoundSampler::SetPlugin(SoundPlugin* lpPlugin)
{
	m_lpPlugin = lpPlugin;
}
void SoundSampler::AddFilter(SoundFilter* lpFilter)
{
	m_Filters.push_back(lpFilter);
}
void SoundSampler::AddPass(SoundPass* lpPass)
{
	m_Passes.push_back(lpPass);
}